home *** CD-ROM | disk | FTP | other *** search
/ Developer CD Series 1996 February: Tool Chest / Apple Developer CD Series Tool Chest February 1996 (Apple Computer)(1996).iso / Sample Code / Snippets / Testing & Debugging / Audit / Src / Failure.h < prev    next >
Encoding:
C/C++ Source or Header  |  1993-07-21  |  4.2 KB  |  145 lines  |  [TEXT/KAHL]

  1. /*
  2.  * Failure.h
  3.  * Copyright © 1992-93, Apple Computer Inc. All Rights Reserved.
  4.  * Simple Failure handler.
  5.  */
  6.  
  7. #ifndef _H_Failure
  8. #define _H_Failure
  9. #include <setjmp.h>
  10. #include <Types.h>
  11.  
  12. /*
  13.  * The FailureRecord contains the information we need to
  14.  * manage and, possibly, recover from errors. 
  15.  */
  16. typedef struct FailureRecord {
  17.     jmp_buf            jmpBuf;
  18.     OSErr            status;
  19.     short            messageIndex;
  20. } FailureRecord, *FailureRecordPtr;
  21.  
  22. /*
  23.  * This is a slightly simplified implementation of the Think/MPW/whatever
  24.  * "Failure" mechanism. To use, define error handlers using the following macros:
  25.  *    TRY {                        initialize a failure unit.
  26.  *    } CATCH {                    end of the "normal" sequence, begin error handler.
  27.  *    } ENDTRY;                    end of the error unit.
  28.  *    NO_PROPAGATE                (Inside the CATCH segment: do not pass the error
  29.  *                                to the higher-level).
  30.  *    Failure(status, message)    Initiate error recovery.
  31.  *    FailNIL(ptr/handle)            Error if thing is NULL
  32.  *    FailOSErr(status, message)    Error if status != noErr
  33.  *    SET_MESSAGE(message)        Sets the message index if non currently specified.
  34.  * If an error is not caught (in a sequence with NO_PROPAGATE), it will eventually
  35.  * force an error alert with the indicated message.
  36.  */
  37. #define FATAL        (TRUE)
  38. #define NON_FATAL    (FALSE)
  39. #define TRY    {                                                        \
  40.         FailureRecordPtr    __oldFailurePtr;                        \
  41.         FailureRecord        __failureRecord;                        \
  42.         __oldFailurePtr = gFailurePtr;                                \
  43.         gFailurePtr = &__failureRecord;                                \
  44.         if ((__failureRecord.status                                    \
  45.             = setjmp(__failureRecord.jmpBuf)) == noErr) {
  46.             /* Normal code here */
  47.  
  48. #define CATCH                                                        \
  49.         } else {
  50.             /* Error handler here */
  51. #define ENDTRY                                                        \
  52.             }                                                        \
  53.             gFailurePtr = __oldFailurePtr;                            \
  54.             if (__failureRecord.status != noErr) {                    \
  55.                 FailureNeverDebug(                                    \
  56.                     __failureRecord.status,                            \
  57.                     __failureRecord.messageIndex                    \
  58.                 );                                                    \
  59.             }                                                        \
  60.         }
  61.  
  62. #define STATUS            (gFailurePtr->status)
  63. #define MESSAGE            (gFailurePtr->messageIndex)
  64. #define NO_PROPAGATE do {                                            \
  65.         gFailurePtr->status = noErr;                                \
  66.     } while (0)
  67.     
  68. #ifdef THINK_C
  69. #define Failure(status, message) do {                                \
  70.         gFailureLine = __LINE__;                                    \
  71.         gFailureFile = "\p" __FILE__;                                \
  72.         __Failure(status, message);                                    \
  73.     } while (0)
  74. #define FailOSErr(status, message) do {                                \
  75.         OSErr            _status = (status);                            \
  76.         if (_status != noErr) {                                        \
  77.             Failure(_status, message);                                \
  78.         }                                                            \
  79.     } while (0)
  80. #define FailOSErrNeverDebug(status, message) do {                    \
  81.         OSErr            _status = (status);                            \
  82.         if (_status != noErr) {                                        \
  83.             gFailureLine = __LINE__;                                \
  84.             gFailureFile = "\p" __FILE__;                            \
  85.             FailureNeverDebug(_status, message);                    \
  86.         }                                                            \
  87.     } while (0)
  88. #define FailNIL(what, message) do {                                    \
  89.         if ((what) == NULL) {                                        \
  90.             gFailureLine = __LINE__;                                \
  91.             gFailureFile = "\p" __FILE__;                            \
  92.             __FailNIL(message);                                        \
  93.         }                                                            \
  94.     } while (0)
  95. #else
  96. /*
  97.  * MPW can't handle __FILE__ in macros.
  98.  */
  99. #define Failure(status, message) do {                                \
  100.         gFailureLine = __LINE__;                                    \
  101.         gFailureFile = "\p";                                        \
  102.         __Failure(status, message);                                    \
  103.     } while (0)
  104. #define FailOSErr(status, message) do {                                \
  105.         OSErr            _status = (status);                            \
  106.         if (_status != noErr) {                                        \
  107.             Failure(_status, message);                                \
  108.         }                                                            \
  109.     } while (0)
  110. #define FailOSErrNeverDebug(status, message) do {                    \
  111.         OSErr            _status = (status);                            \
  112.         if (_status != noErr) {                                        \
  113.             gFailureLine = __LINE__;                                \
  114.             gFailureFile = "\p";                                    \
  115.             FailureNeverDebug(_status, message);                    \
  116.         }                                                            \
  117.     } while (0)
  118. #define FailNIL(what, message) do {                                    \
  119.         if ((what) == NULL) {                                        \
  120.             gFailureLine = __LINE__;                                \
  121.             gFailureFile = "\p";                                    \
  122.             __FailNIL(message);                                        \
  123.         }                                                            \
  124.     } while (0)
  125. #endif
  126.  
  127. void                        __Failure(
  128.         OSErr            errorStatus,
  129.         short            messageIndex
  130.     );
  131. void                        FailureNeverDebug(
  132.         OSErr            errorStatus,
  133.         short            messageIndex
  134.     );
  135. void                        __FailNIL(
  136.         short            messageIndex
  137.     );
  138.  
  139. extern StringPtr            gFailureFile;
  140. extern long                    gFailureLine;
  141. extern FailureRecordPtr        gFailurePtr;
  142. extern Boolean                gDebugOnError;
  143.  
  144. #endif
  145.